package com.maint.m

import android.content.pm.ActivityInfo
import android.os.Build
import android.os.Bundle
import java.util.concurrent.CountDownLatch
import android.os.Handler
import android.os.Looper
import android.util.Log
import android.view.View
import android.widget.Toast
import androidx.activity.enableEdgeToEdge
import androidx.core.os.postDelayed
import com.maint.m.databinding.ActivityVideoBinding
import com.maint.m.glsurface.NV21ToH264Encoder
import com.rokid.security.phone.sdk.api.PSecuritySDK
import com.rokid.security.phone.sdk.api.msg.listener.IMessageListener
import java.io.File
import com.maint.m.utils.H264RtpStreamer


import com.maint.m.utils.XunfeiTtsUtil
import com.maint.m.utils.AppDataManager
import java.io.Serializable
import androidx.lifecycle.ViewModelProvider
import com.maint.m.viewmodel.VideoViewModel

class VideoActivity : BaseActivity() {
    private val TAG = "VideoActivity::"
    private lateinit var binding: ActivityVideoBinding
    private lateinit var encoder: NV21ToH264Encoder
    private lateinit var streamer: H264RtpStreamer

    private val mainHandler = Handler(Looper.getMainLooper())
    private var operationArray: Array<String>? = null // 操作项数组，用于按顺序播报
    private val operationDelay = 15000L // 操作项之间的延迟时间（毫秒）
    private var originalQueueSize = 0 // 原始队列大小，用于计算操作步骤编号
    private var currentOperationIndex = 0 // 当前处理的操作项索引

    private var ticketId: String? = null
    private val viewModel: VideoViewModel by lazy {
        ViewModelProvider(this).get(VideoViewModel::class.java)
    }

    // WebSocket 消息处理器
    private val webSocketHandler = object : SimpleWebSocketHandler {
        override fun onMessageReceived(type: WebSocketMessageType, message: String) {
            Log.i("WebSocket-Video", "收到消息: $message")

            try {
                // 解析JSON响应
                val jsonObject = org.json.JSONObject(message)
                val business = jsonObject.getInt("business")
                Log.i(TAG, "业务类型: $business")



                // 处理开关站识别消息 (business = 2)
                if (business == 2) {
                    val data = jsonObject.optString("data", "")
                    Log.i(TAG, "收到开关站信息: $data")

                    // 判断条件：business=2 且 data不为空
                    if (data.isNotEmpty()) {
                        Log.i(TAG, "开始识别开关柜流程")
                        // 生成音频并发送
                        generateAndSendAudio("开关站识别成功，您已到达${data}", "开关站识别成功，您已到达${data}")
                        mainHandler.postDelayed({
                            generateAndSendAudio("请确认操作间隔是否正确", "请确认操作间隔是否正确")
                        }, 15000)
                    }
                }
                else if (business == 3) {
                    val data = jsonObject.optString("data", "")
                    Log.i(TAG, "收到电气柜信息: $data")

                    // 判断条件：business=3 且 data不为空
                    if (data.isNotEmpty()) {
                        Log.i(TAG, "收到business=3消息，开始处理缓存操作项流程")
                        
                        // 使用一个单一的延时序列，避免多个独立延时器可能导致的时序问题
                        object : Runnable {
                            private var step = 0
                            
                            override fun run() {
                                step++
                                Log.i(TAG, "执行流程步骤：$step")
                                
                                when (step) {
                                    1 -> {
                                        // 第一步：初始音频
                                        Log.i(TAG, "步骤1：播放操作间隔正确提示音")
                                        generateAndSendAudio("操作间隔正确", "操作间隔正确")
                                        mainHandler.postDelayed(this, 5000) // 5秒后执行下一步
                                    }
                                    2 -> {
                                        // 第二步：开关标签识别
                                        Log.i(TAG, "步骤2：播放开关标签识别提示音")
                                        generateAndSendAudio("开始识别开关柜开关标签", "开始识别开关柜开关标签")
                                        mainHandler.postDelayed(this, 6000) // 5秒后执行下一步
                                    }
                                    3 -> {
                                        // 第三步：标签对比成功
                                        Log.i(TAG, "步骤3：播放标签对比成功提示音")
                                        generateAndSendAudio("开关柜开关标签对比成功", "开关柜开关标签对比成功")
                                        mainHandler.postDelayed(this, 15000) // 3秒后执行下一步
                                    }
                                    4 -> {
                                        // 第四步：操作开始提示
                                        Log.i(TAG, "步骤4：播放操作开始提示音")
                                        generateAndSendAudio("下面开始对操作项目进行操作", "")
                                        mainHandler.postDelayed(this, 4000) // 2秒后执行下一步
                                    }
                                    5 -> {
                                        // 第五步：加载并开始播报缓存操作项
                                        Log.i(TAG, "步骤5：准备加载并播报缓存操作项")

                                        // 创建一个后台线程来处理整个播报流程，避免阻塞UI线程
                                        Thread {
                                            try {
                                                // 1. 加载操作项数组
                                                val itemsArray = loadOperationItemsFromCache()
                                                   
                                                // 2. 记录数组内容
                                                Log.i(TAG, "加载后数组大小：${itemsArray.size}")
                                                for (i in itemsArray.indices) {
                                                    Log.i(TAG, "数组项[${i+1}]: ${itemsArray[i]}")
                                                }
                                                   
                                                if (itemsArray.isNotEmpty()) {
                                                    val localQueueSize = itemsArray.size
                                                    
                                                    Log.i(TAG, "准备开始播报，共${localQueueSize}个操作项")
                                                    
                                                    // 延迟一小段时间，然后开始播报流程
                                                    Thread.sleep(500)
                                                    
                                                    // 5. 开始按顺序播报所有操作项
                                                    for (index in itemsArray.indices) {
                                                        val currentOp = itemsArray[index]
                                                        val currentStep = index + 1
                                                          
                                                        Log.i(TAG, "处理操作项: '$currentOp', 当前为第${currentStep}步")
                                                          
                                                        if (currentOp.trim().isNotEmpty()) {
                                                            // 设置音频文本（包含步骤标识）和展示文本（仅纯文本）
                                                            val audioText = if (index == itemsArray.size - 1) {
                                                                "最后一步: ${currentOp.trim()}"
                                                            } else {
                                                                "第${currentStep}步: ${currentOp.trim()}"
                                                            }
                                                            val displayText = currentOp.trim()
                                                            Log.i(TAG, "准备播报: '$audioText', 展示文本: '$displayText'")
                                                             
                                                            // 使用同步方式等待音频真正完成，而不仅仅是方法调用完成
                                                            val audioCompleteLatch = CountDownLatch(1)
                                                             
                                                            mainHandler.post {
                                                                try {
                                                                    // 为每个操作项创建一个同步的音频生成和发送过程
                                                                    generateAndSendAudioSync(audioText, displayText) {
                                                                        // 音频完成回调
                                                                        Log.i(TAG, "音频播报实际完成: $audioText")
                                                                        audioCompleteLatch.countDown()
                                                                    }
                                                                } catch (e: Exception) {
                                                                    Log.e(TAG, "生成音频时发生异常: ${e.message}", e)
                                                                    audioCompleteLatch.countDown() // 即使出错也要确保latch被释放
                                                                }
                                                            }
                                                             
                                                            // 等待音频真正完成生成和发送
                                                            audioCompleteLatch.await()
                                                        }
                                                          
                                                        // 如果不是最后一项，等待指定的延迟时间
                                                        if (index < itemsArray.size - 1) {
                                                            Log.i(TAG, "等待${operationDelay}毫秒后处理下一个操作项")
                                                            Thread.sleep(operationDelay)
                                                        } else {
                                                            // 最后一项额外等待更长时间，确保音频完全播放完毕
                                                            Log.i(TAG, "最后一项额外等待1500毫秒，确保音频完全播放")
                                                            Thread.sleep(1500)
                                                        }
                                                    }
                                                    
                                                    Log.i(TAG, "所有${itemsArray.size}个操作项已处理完毕，准备播放完成提示")
                                                    
                                                    // 所有操作项处理完毕后，语音提示操作完成
                                                    mainHandler.post {
                                                        try {
                                                            val audioCompleteText = "操作完毕"
                                                            val displayCompleteText = "操作完毕"
                                                            Log.i(TAG, "准备播报完成提示: '$audioCompleteText', 展示文本: '$displayCompleteText'")
                                                            generateAndSendAudioSync(audioCompleteText, displayCompleteText) {
                                                                // 完成提示音频也同步等待完成
                                                                Log.i(TAG, "操作完毕提示音频播报完成")
                                                                 
                                                                // 仅在所有音频都完成后重置共享状态变量为安全值
                                                                Log.i(TAG, "重置共享状态变量")
                                                                operationArray = null
                                                                originalQueueSize = 0
                                                                currentOperationIndex = 0
                                                            }
                                                        } catch (e: Exception) {
                                                            Log.e(TAG, "生成操作完成提示音频时发生异常: ${e.message}", e)
                                                            // 出错时也要重置状态
                                                            operationArray = null
                                                            originalQueueSize = 0
                                                            currentOperationIndex = 0
                                                        }
                                                    }
                                                } else {
                                                    Log.i(TAG, "警告：数组加载后为空，无法开始播报")
                                                    
                                                    // 在UI线程重置状态
                                                    mainHandler.post {
                                                        operationArray = null
                                                        currentOperationIndex = 0
                                                        originalQueueSize = 0
                                                    }
                                                }
                                            } catch (e: Exception) {
                                                Log.e(TAG, "处理缓存操作项时发生异常: ${e.message}", e)
                                                
                                                // 发生异常时，在UI线程重置状态
                                                mainHandler.post {
                                                    operationArray = null
                                                    currentOperationIndex = 0
                                                    originalQueueSize = 0
                                                }
                                            }
                                        }.start()
                                    }
                                }
                            }
                        }.run() // 立即开始执行流程
                    }
                }
//                else if (business == 4) {
//                    val data = jsonObject.optString("data", "")
//                    Log.i(TAG, "收到操作项列表信息: $data")
//
//                    // 判断条件：business=4 且 data不为空
//                    if (data.isNotEmpty()) {
//                        Log.i(TAG, "开始处理操作项列表")
//                        generateAndSendAudio("操作间隔正确", "操作间隔正确")
//                        mainHandler.postDelayed({
//                            generateAndSendAudio("开始识别开关柜开关标签", "开始识别开关柜开关标签")
//                        }, 15000)
//                    }
//                }

            } catch (e: Exception) {
                Log.e(TAG, "解析WebSocket消息失败: ${e.message}", e)
            }
        }

        override fun onConnectionChanged(connected: Boolean) {
            Log.i(TAG, "WebSocket连接状态: ${if (connected) "已连接" else "未连接"}")
        }

        override fun onError(errorMsg: String) {
            Log.e(TAG, "WebSocket错误: $errorMsg")
        }
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE

        super.onCreate(savedInstanceState)
        enableEdgeToEdge()
        binding = ActivityVideoBinding.inflate(layoutInflater)
        setContentView(binding.root)

        PSecuritySDK.getMessageService()?.addMessageListener(mMessageListener)

        val outputFile = File(getExternalFilesDir(null), "output.h264")
        encoder = NV21ToH264Encoder(480, 400, outputFile)
        encoder.start()

        // 初始化RTP流发送器
        streamer = H264RtpStreamer(this)

        // 设置RTMP推流地址并开始推流
        // 注意：由于BuildConfig中没有DEFAULT_RTMP_URL常量，使用配置参数
        try {
            // 可以通过参数传递给streamer，或者让streamer从配置文件读取
            streamer.startPush()
            Log.i(TAG, "已开始RTMP推流到线上服务器")
        } catch (e: Exception) {
            Log.e(TAG, "启动RTMP推流失败: ${e.message}", e)
        }


        PSecuritySDK.getMessageService()?.sendTextMessageByP2P("开始")

        ticketId = intent.getStringExtra("ticket_id")
        
        // 观察ViewModel的数据变化
        observeViewModel()
    }
    
    private fun observeViewModel() {
        viewModel.updateSuccess.observe(this) {
            if (it) {
                finish()
            }
        }
        
        viewModel.errorMessage.observe(this) {
            it?.let {
                Log.e(TAG, "网络错误: $it")
            }
        }
    }

    private val mMessageListener = object : IMessageListener {
        override fun onNv21Data(data: ByteArray, width: Int, height: Int) {
            super.onNv21Data(data, width, height)
            // 保留NV21格式预览功能
            binding.videoSurfaceView.setPreviewData(data, width, height)
        }
        override fun onVideoH264Stream(buffer: java.nio.ByteBuffer) {
            val data = ByteArray(buffer.remaining())
            buffer.get(data)
            if (data.isNotEmpty()) {
                streamer.writeFrame(data)
            }
        }
        override fun onP2PTextMessage(msg: String) {
            super.onP2PTextMessage(msg)
            Log.i(TAG, "收到P2P文本消息: $msg")
            if (msg == "close" && ticketId != null) {
                // 使用ViewModel调用API更新状态
                Log.i(TAG, "调用ViewModel更新票据状态，ID: $ticketId")
                viewModel.updateTicketStatus(ticketId!!, "1")
            }
        }
    }

    override fun onResume() {
        super.onResume()
        // 注册WebSocket处理器
        WebSocketService.getInstance().registerHandler(webSocketHandler, this)
        Log.i(TAG, "WebSocket处理器已注册")
    }

    override fun onPause() {
        super.onPause()
        // 注销WebSocket处理器
        WebSocketService.getInstance().unregisterHandler(webSocketHandler)
        Log.i(TAG, "WebSocket处理器已注销")
    }

    override fun onDestroy() {
        super.onDestroy()

        PSecuritySDK.getMessageService()?.sendTextMessageByP2P("结束")

        // 停止编码器
        try {
            if (::encoder.isInitialized) {
                encoder.stop()
                Log.i(TAG, "编码器已停止")
            }
        } catch (e: Exception) {
            Log.e(TAG, "停止编码器异常", e)
        }

        // 停止RTP流发送
        try {
            if (::streamer.isInitialized) {
                streamer.stopPush()
                Log.i(TAG, "RTP流发送已停止")
            }
        } catch (e: Exception) {
            Log.e(TAG, "停止RTP流发送异常", e)
        }


        PSecuritySDK.getMessageService()?.removeMessageListener(mMessageListener)
        // 确保注销WebSocket处理器
        WebSocketService.getInstance().unregisterHandler(webSocketHandler)
    }


    /**
     * 从缓存加载操作项并返回数组
     */
    private fun loadOperationItemsFromCache(): Array<String> {
        Log.i(TAG, "开始从缓存加载操作项到数组")
        val itemsList = mutableListOf<String>()
        
        try {
            // 从缓存获取操作项
            val rawData = AppDataManager.getOperation<Serializable>("operation_items")
            Log.i(TAG, "从缓存获取操作项数据类型: ${rawData?.javaClass?.name}")
            
            when (rawData) {
                is List<*> -> {
                    // 处理列表类型数据
                    val list = rawData.filterIsInstance<String>()
                    Log.i(TAG, "转换为字符串列表，大小: ${list.size}")
                    itemsList.addAll(list)
                }
                is String -> {
                    // 处理字符串类型数据
                    Log.i(TAG, "缓存数据为字符串，内容: $rawData")
                    // 可以根据需要解析字符串，例如按行分割或其他格式解析
                    val items = rawData.split("\n").filter { it.isNotBlank() }
                    itemsList.addAll(items)
                }
                else -> {
                    // 处理其他类型数据
                    if (rawData != null) {
                        Log.i(TAG, "缓存数据为其他类型，尝试转换为字符串")
                        itemsList.add(rawData.toString())
                    } else {
                        Log.w(TAG, "缓存中没有找到操作项数据")
                    }
                }
            }
        } catch (e: Exception) {
            Log.e(TAG, "解析缓存数据时发生异常: ${e.message}", e)
            
            // 异常情况下也尝试创建一个日志记录
            try {
                val rawData = AppDataManager.getOperation<Serializable>("operation_items")
                Log.e(TAG, "原始缓存数据类型: ${rawData?.javaClass?.name}")
            } catch (innerE: Exception) {
                Log.e(TAG, "无法获取原始缓存数据", innerE)
            }
        }
        
        val itemsArray = itemsList.toTypedArray()
        Log.i(TAG, "loadOperationItemsFromCache方法执行完毕，数组大小: ${itemsArray.size}")
        return itemsArray
    }

    /**
     * 生成音频并发送（异步版本，无回调）
     */
    private fun generateAndSendAudio(longText: String, operationText: String) {
        try {
            Log.i(TAG, "开始生成音频，文本: $longText")

            XunfeiTtsUtil.textToAudio(
                text = longText,
                onAudioReady = { audioData ->
                    Log.i(TAG, "音频生成成功，数据长度: ${audioData.size}字节")
                    runOnUiThread {
                        // 发送文本消息
                        PSecuritySDK.getMessageService()?.sendTextMessageByP2P(operationText)

                        // 发送音频数据
                        PSecuritySDK.getMessageService()?.sendAudioStreamDataByP2P(audioData)
                        Log.i(TAG, "已发送音频数据")

                        Log.i(TAG, "已发送文本消息: $operationText")
                    }
                },
                onError = { errorMsg ->
                    Log.e(TAG, "语音生成失败: $errorMsg")
                },
            )
        } catch (e: Exception) {
            Log.e(TAG, "生成和发送音频过程中出现异常: ${e.message}", e)
        }
    }
    
    /**
     * 生成音频并发送（带完成回调版本）
     * 确保音频真正完成生成和发送后才调用回调
     */
    private fun generateAndSendAudioSync(longText: String, operationText: String, onComplete: () -> Unit) {
        try {
            Log.i(TAG, "开始同步生成音频，文本: $longText")

            XunfeiTtsUtil.textToAudio(
                text = longText,
                onAudioReady = { audioData ->
                    Log.i(TAG, "音频生成成功，数据长度: ${audioData.size}字节")
                    runOnUiThread {
                        try {
                            // 发送文本消息
                            PSecuritySDK.getMessageService()?.sendTextMessageByP2P(operationText)
                            Log.i(TAG, "已发送文本消息: $operationText")

                            // 发送音频数据
                            PSecuritySDK.getMessageService()?.sendAudioStreamDataByP2P(audioData)
                            Log.i(TAG, "已发送音频数据")
                        } catch (e: Exception) {
                            Log.e(TAG, "发送音频或文本消息时发生异常: ${e.message}", e)
                        } finally {
                            // 无论成功失败，都调用完成回调
                            onComplete()
                        }
                    }
                },
                onError = { errorMsg ->
                    Log.e(TAG, "语音生成失败: $errorMsg")
                    runOnUiThread {
                        // 即使出错，也要调用完成回调
                        onComplete()
                    }
                },
            )
        } catch (e: Exception) {
            Log.e(TAG, "生成和发送音频过程中出现异常: ${e.message}", e)
            // 捕获异常时也调用完成回调，避免阻塞
            onComplete()
        }
    }

    /**
     * 定时发送下一个操作项，使用数组下标访问
     */
    private fun scheduleNextOperation() {
        Log.i(TAG, "进入scheduleNextOperation方法，开始处理操作项数组")
        
        // 检查操作项数组是否存在
        val itemsArray = operationArray
        if (itemsArray == null) {
            Log.e(TAG, "操作项数组为空，无法继续处理")
            return
        }
        
        // 记录当前状态
        Log.i(TAG, "当前索引: $currentOperationIndex, 数组大小: ${itemsArray.size}, 原始队列大小: $originalQueueSize")
        
        try {
            // 检查是否还有未处理的操作项
            if (currentOperationIndex < itemsArray.size) {
                // 获取当前操作项
                val currentOp = itemsArray[currentOperationIndex]
                val currentStep = currentOperationIndex + 1 // 步骤从1开始计数
                
                Log.i(TAG, "获取操作项: '$currentOp', 当前为第${currentStep}步")
                
                // 处理当前操作项
                if (currentOp.trim().isNotEmpty()) {
                    val operationText = "第${currentStep}步: ${currentOp.trim()}"
                    Log.i(TAG, "准备播报第${currentStep}步: '$operationText'")
                    
                    // 生成并发送当前操作项的音频和文本
                    generateAndSendAudio(operationText, operationText)
                    Log.i(TAG, "已发送第${currentStep}步音频播报请求")
                    
                    // 增加当前索引
                    currentOperationIndex++
                    
                    // 如果还有剩余操作项，安排下一个操作项的处理
                    if (currentOperationIndex < itemsArray.size) {
                        val remainingOpCount = itemsArray.size - currentOperationIndex
                        Log.i(TAG, "还有${remainingOpCount}个操作项待处理，计划延时${operationDelay}毫秒后处理下一个")
                        
                        // 使用Handler延迟执行下一个操作项
                        mainHandler.postDelayed({
                            Log.i(TAG, "延迟时间到，准备处理第${currentOperationIndex + 1}步")
                            scheduleNextOperation()
                        }, operationDelay)
                    } else {
                        Log.i(TAG, "所有${originalQueueSize}个操作项已处理完毕")
                        // 处理完毕后重置状态
                        operationArray = null
                        currentOperationIndex = 0
                        originalQueueSize = 0
                    }
                } else {
                    Log.w(TAG, "当前操作项为空或仅包含空白字符，跳过此步骤")
                    // 增加索引，跳过空项，立即处理下一个
                    currentOperationIndex++
                    scheduleNextOperation() // 立即处理下一个，不延迟
                }
            } else {
                Log.i(TAG, "所有操作项已处理完毕，索引超出范围")
                // 处理完毕后重置状态
                operationArray = null
                currentOperationIndex = 0
                originalQueueSize = 0
            }
        } catch (e: Exception) {
            Log.e(TAG, "处理操作项时发生异常: ${e.message}", e)
            // 发生异常时，记录错误并重置状态
            Log.e(TAG, "异常索引: $currentOperationIndex, 数组长度: ${itemsArray.size}")
            // 重置状态，避免卡在异常状态
            operationArray = null
            currentOperationIndex = 0
            originalQueueSize = 0
        }
    }
}
